/*!	 widget_color.cpp
**	 Template File
**
**	Copyright (c) 2002-2005 Robert B. Quattlebaum Jr., Adrian Bentley
**
**	This package is free software; you can redistribute it and/or
**	modify it under the terms of the GNU General Public License as
**	published by the Free Software Foundation; either version 2 of
**	the License, or (at your option) any later version.
**
**	This package is distributed in the hope that it will be useful,
**	but WITHOUT ANY WARRANTY; without even the implied warranty of
**	MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
**	General Public License for more details.
**
*/

#ifdef USING_PCH
#	include "pch.h"
#else
#ifdef HAVE_CONFIG_H
#	include <config.h>
#endif

#include <synfig/general.h>

#include "widgets/widget_color.h"
#include <cmath>
#include "app.h"
#include <gtkmm/drawingarea.h>

#include <gui/localization.h>

#endif

using namespace std;
using namespace etl;
using namespace synfig;
using namespace studio;

synfig::Color
studio::colorconv_apply_gamma(const synfig::Color &c_)
{
    const synfig::Color c(c_.clamped());
    return synfig::Color(
               App::gamma.r_F32_to_F32(c.get_r()),
               App::gamma.g_F32_to_F32(c.get_g()),
               App::gamma.b_F32_to_F32(c.get_b()),
               c.get_a());
}

void
studio::render_color_to_window(const Cairo::RefPtr<Cairo::Context> &cr, const Gdk::Rectangle &ca, const synfig::Color &color)
{
    const int height(ca.get_height());
    const int width(ca.get_width());

    const int square_size(height / 2);

    if (color.get_alpha() != 1.0) {
        // In this case we need to render the alpha squares

        const Color bg1(
            colorconv_apply_gamma(
                Color::blend(color, Color(0.75, 0.75, 0.75), 1.0).clamped()));
        const Color bg2(
            colorconv_apply_gamma(
                Color::blend(color, Color(0.5, 0.5, 0.5), 1.0).clamped()));

        bool toggle(false);

        for (int i = 0; i < width; i += square_size) {
            const int square_width(min(square_size, width - i));

            if (toggle) {
                cr->set_source_rgb(bg1.get_r(), bg1.get_g(), bg1.get_b());
                cr->rectangle(ca.get_x() + i, ca.get_y(), square_width, square_size);
                cr->fill();

                cr->set_source_rgb(bg2.get_r(), bg2.get_g(), bg2.get_b());
                cr->rectangle(ca.get_x() + i, ca.get_y() + square_size, square_width, square_size);
                cr->fill();
                toggle = false;
            } else {
                cr->set_source_rgb(bg2.get_r(), bg2.get_g(), bg2.get_b());
                cr->rectangle(ca.get_x() + i, ca.get_y(), square_width, square_size);
                cr->fill();

                cr->set_source_rgb(bg1.get_r(), bg1.get_g(), bg1.get_b());
                cr->rectangle(ca.get_x() + i, ca.get_y() + square_size, square_width, square_size);
                cr->fill();
                toggle = true;
            }
        }
    } else {
        synfig::Color c = colorconv_apply_gamma(color);
        cr->set_source_rgb(c.get_r(), c.get_g(), c.get_b());
        cr->rectangle(ca.get_x(), ca.get_y(), width - 1, height - 1);
        cr->fill();
    }

    cr->set_source_rgb(1.0, 1.0, 1.0);
    cr->rectangle(ca.get_x() + 1, ca.get_y() + 1, width - 3, height - 3);
    cr->stroke();

    cr->set_source_rgb(0.0, 0.0, 0.0);
    cr->rectangle(ca.get_x(), ca.get_y(), width - 1, height - 1);
    cr->stroke();
}

Widget_Color::Widget_Color()
{
    color = Color(0, 0, 0, 0);
    set_size_request(-1, 16);
    add_events(Gdk::BUTTON_PRESS_MASK | Gdk::BUTTON_RELEASE_MASK);

}

Widget_Color::~Widget_Color()
{
}

void
Widget_Color::set_value(const synfig::Color &data)
{
    assert(data.is_valid());
    color = data;
    queue_draw();
}

const synfig::Color &
Widget_Color::get_value()
{
    assert(color.is_valid());
    return color;
}

bool
Widget_Color::on_event(GdkEvent *event)
{
    switch (event->type) {
    case GDK_BUTTON_PRESS:
        if (event->button.button == 1) {
            signal_activate_();
            return true;
        }

        if (event->button.button == 2) {
            signal_middle_click_();
            return true;
        }

        if (event->button.button == 3) {
            signal_right_click_();
            return true;
        }

        break;

    default:
        break;
    }

    return false;
}

bool
Widget_Color::on_draw(const Cairo::RefPtr<Cairo::Context> &cr)
{
    render_color_to_window(cr, Gdk::Rectangle(0, 0, get_width(), get_height()), color);
    return true;
}